home *** CD-ROM | disk | FTP | other *** search
/ Languguage OS 2 / Languguage OS II Version 10-94 (Knowledge Media)(1994).ISO / gnu / oleo-1_4.lha / oleo-1.4 / eval.c < prev    next >
C/C++ Source or Header  |  1993-05-21  |  34KB  |  1,756 lines

  1. /*    Copyright (C) 1990, 1992, 1993 Free Software Foundation, Inc.
  2.  
  3. This file is part of Oleo, the GNU Spreadsheet.
  4.  
  5. Oleo is free software; you can redistribute it and/or modify
  6. it under the terms of the GNU General Public License as published by
  7. the Free Software Foundation; either version 2, or (at your option)
  8. any later version.
  9.  
  10. Oleo is distributed in the hope that it will be useful,
  11. but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  13. GNU General Public License for more details.
  14.  
  15. You should have received a copy of the GNU General Public License
  16. along with Oleo; see the file COPYING.  If not, write to
  17. the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.  */
  18.  
  19. #include <ctype.h>
  20. #include <stdio.h>
  21.  
  22. #ifdef __TURBOC__
  23. #define SMALLEVAL
  24. #endif
  25.  
  26. #include "funcdef.h"
  27.  
  28. #define obstack_chunk_alloc ck_malloc
  29. #define obstack_chunk_free free
  30. #include "obstack.h"
  31.  
  32. #include "sysdef.h"
  33. #include "global.h"
  34. #include "cell.h"
  35. #include "eval.h"
  36. #include "errors.h"
  37.  
  38. #if defined(HAVE_RINT)
  39. #ifdef __STDC__
  40. extern double rint (double);
  41. extern long random (void);
  42. #else
  43. extern double rint ();
  44. extern long random ();
  45. #endif
  46. #else
  47. #define rint(x) (((x)<0) ? ceil((x)-.5) : floor((x)+.5))
  48. #endif
  49.  
  50.  
  51.  
  52. extern int n_usr_funs;
  53.  
  54.  
  55.  
  56.  
  57. double to_int ();
  58. static int deal_area ();
  59. static void add_int ();
  60. static void add_flt ();
  61. #ifndef __TURBOC__
  62. RETSIGTYPE math_sig ();
  63. #endif
  64.  
  65. #ifdef __STDC__
  66. int fls (long);
  67. #else
  68. int fls ();
  69. #endif
  70. #ifdef SMALLEVAL
  71. int __to_flt (struct value *);
  72. int __to_int (struct value *);
  73. int __to_num (struct value *);
  74. int __to_str (struct value *);
  75. int __to_bol (struct value *);
  76. int __to_rng (struct value *);
  77. #endif
  78.  
  79.  
  80.  
  81. struct value
  82.   {
  83.     int type;
  84.     union vals x;
  85.   };
  86.  
  87. #define Float    x.c_d
  88. #define String    x.c_s
  89. #define Int    x.c_l
  90. #define Value    x.c_i
  91. #define Rng    x.c_r
  92.  
  93. #undef PI
  94. #define PI (3.14159265358979326848)
  95.  
  96. static struct value *stack;
  97. static int stackmax;
  98. static int curstack;
  99.  
  100. unsigned short current_cycle;
  101.  
  102. CELLREF cur_row;
  103. CELLREF cur_col;
  104.  
  105. static double exp10_arr[] =
  106. {
  107.   1E0, 1E1, 1E2, 1E3, 1E4,
  108.   1E5, 1E6, 1E7, 1E8, 1E9,
  109.   1E10, 1E11, 1E12, 1E13, 1E14,
  110.   1E15, 1E16, 1E17, 1E18, 1E19,
  111.   1E20, 1E21, 1E22, 1E23, 1E24,
  112.   1E25, 1E26, 1E27, 1E28, 1E29
  113. };
  114.  
  115. /* Various math conversions with error checking */
  116. #define I_ADD(i1,i2) {    itmp=(i1)+(i2);                    \
  117.             if((i1>0)==(i2>0) && (itmp>0)!=(i1>0)) {    \
  118.                 p->Float=(double)(i1)+(double)(i2);    \
  119.                 p->type=TYP_FLT;            \
  120.             } else                        \
  121.                 p->Int=itmp;    }
  122.  
  123. #define I_SUB(i1,i2) {    itmp=(i1)-(i2);                    \
  124.             if(((i1)<0)==((i2)>0) && ((itmp)>0)!=((i2)<0)) {\
  125.                 p->Float=(double)(i1)-(double)(i2);    \
  126.                 p->type=TYP_FLT;            \
  127.             } else                        \
  128.                 p->Int=itmp;    }
  129.  
  130. #define I_DIV(i1,i2) {    ftmp=(double)(i1)/(double)(i2);            \
  131.             /* ... */;                    \
  132.             p->Float=ftmp;                    \
  133.             p->type=TYP_FLT;    }
  134.  
  135. #define I_MOD(i1,i2) {itmp=(i1)%(i2);/* ... */;p->Int=itmp;}
  136.  
  137. #define I_MUL(i1,i2) {    if(fls(i1)+fls(i2)>32) {            \
  138.                 p->Float=(double)(i1)*(double)(i2);    \
  139.                 p->type=TYP_FLT;            \
  140.             } else                        \
  141.                 p->Int=(i1)*(i2);    }
  142.  
  143. #define F_ADD(f1,f2) {    ftmp=(f1)+(f2);/* ... */;p->Float=ftmp;    }
  144.  
  145. #define F_SUB(f1,f2) {    ftmp=(f1)-(f2);/* ... */;p->Float=ftmp;}
  146.  
  147. #define F_DIV(f1,f2) {    ftmp=(f1)/(f2);/* ... */;p->Float=ftmp;}
  148.  
  149. #define F_MOD(f1,f2) {    itmp=(long)(f1)%(long)(f2);/* ... */;p->Int=itmp;p->type=TYP_INT;}
  150.  
  151. #define F_MUL(f1,f2) {    ftmp=(f1)*(f2);/* ... */;p->Float=ftmp;}
  152.  
  153. double ftmp;
  154. long itmp;
  155. int overflow;
  156.  
  157. /* You may ask:  Why not jsut put the value in stack[0] and goto break_out
  158.    The answer is that ERROR is a valid input type for several operators, so
  159.    we want to work if we're feeding an error into one of these operators. . .
  160.  */
  161. #define ERROR(cause)        \
  162.     {            \
  163.         p->type=TYP_ERR;\
  164.         p->Value=cause; \
  165.         goto next_byte; \
  166.     }
  167.  
  168. #ifdef SMALLEVAL
  169.  
  170. #define TO_FLT(val)            \
  171.     if((tmp=__to_flt(val))!=0)    \
  172.         ERROR(tmp);
  173.  
  174. #define TO_INT(val)            \
  175.     if((tmp=__to_int(val))!=0)    \
  176.         ERROR(tmp);
  177.  
  178. #define TO_NUM(val)            \
  179.     if((tmp=__to_num(val))!=0)    \
  180.         ERROR(tmp);
  181.  
  182. #define TO_STR(val)            \
  183.     if((tmp=__to_str(val))!=0)    \
  184.         ERROR(tmp);
  185.  
  186. #define TO_BOL(val)            \
  187.     if((tmp=__to_bol(val))!=0)    \
  188.         ERROR(tmp);
  189.  
  190. #define TO_RNG(val)            \
  191.     if((tmp=__to_rng(val))!=0)    \
  192.         ERROR(tmp);
  193.  
  194. #else
  195. #define TO_FLT(val)    \
  196.     if((val)->type==TYP_FLT) \
  197.         ; \
  198.     else if((val)->type==TYP_INT) { \
  199.         (val)->type=TYP_FLT; \
  200.         (val)->Float=(double)(val)->Int; \
  201.     } else if((val)->type==TYP_STR) { \
  202.         (val)->type=TYP_FLT; \
  203.         strptr=(val)->String; \
  204.         (val)->Float=astof(&strptr); \
  205.         if(*strptr) \
  206.             ERROR(NON_NUMBER); \
  207.     } else if((val)->type==TYP_ERR) {\
  208.         ERROR((val)->Value); \
  209.     } else if((val)->type==0) { \
  210.         (val)->type=TYP_FLT; \
  211.         (val)->Float=0.0; \
  212.     } else \
  213.         ERROR(NON_NUMBER);
  214.  
  215. #define TO_INT(val)    \
  216.     if((val)->type==TYP_INT) \
  217.         ; \
  218.     else if((val)->type==TYP_FLT) { \
  219.         (val)->type=TYP_INT; \
  220.         (val)->Int=(long)(val)->Float; \
  221.     } else if((val)->type==TYP_STR) { \
  222.         (val)->type=TYP_INT; \
  223.         strptr=(val)->String; \
  224.         (val)->Int=astol(&strptr); \
  225.         if(*strptr) \
  226.             ERROR(NON_NUMBER); \
  227.     } else if((val)->type==TYP_ERR) {\
  228.         ERROR((val)->Value); \
  229.     } else if((val)->type==0) { \
  230.         (val)->type=TYP_INT; \
  231.         (val)->Int=0; \
  232.     } else \
  233.         ERROR(NON_NUMBER);
  234.  
  235. #define TO_NUM(val)    \
  236.     if((val)->type==TYP_INT || (val)->type==TYP_FLT) \
  237.         ; \
  238.     else if((val)->type==TYP_STR) { \
  239.         (val)->type=TYP_FLT; \
  240.         strptr=(val)->String; \
  241.         (val)->Float=astof(&strptr); \
  242.         if(*strptr) \
  243.             ERROR(NON_NUMBER); \
  244.     } else if((val)->type==TYP_ERR) {\
  245.         ERROR((val)->Value); \
  246.     } else if((val)->type==0) { \
  247.         (val)->type=TYP_INT; \
  248.         (val)->Int=0; \
  249.     } else \
  250.         ERROR(NON_NUMBER);
  251.  
  252. #define TO_STR(val)    \
  253.     if((val)->type==TYP_STR)    \
  254.         ;    \
  255.     else if((val)->type==TYP_INT) {    \
  256.         char *s;    \
  257.         (val)->type=TYP_STR;    \
  258.         s=obstack_alloc(&tmp_mem,30); \
  259.         sprintf(s,"%ld",(val)->Int); \
  260.         (val)->String=s;    \
  261.     } else if((val)->type==TYP_FLT) {        \
  262.         char *s;                \
  263.         s=flt_to_str((val)->Float);        \
  264.         (void)obstack_grow(&tmp_mem,s,strlen(s)+1); \
  265.         (val)->String=obstack_finish(&tmp_mem);    \
  266.         (val)->type=TYP_STR;            \
  267.     } else if((val)->type==TYP_ERR) {        \
  268.         ERROR((val)->Value);    \
  269.     } else if((val)->type==0) {    \
  270.         (val)->type=TYP_STR;    \
  271.         (val)->String=obstack_alloc(&tmp_mem,1); \
  272.         (val)->String[0]='\0'; \
  273.     } else \
  274.         ERROR(NON_STRING);
  275.  
  276. #define TO_BOL(val)    \
  277.     if((val)->type==TYP_BOL)    \
  278.         ;    \
  279.     else if((val)->type==TYP_ERR) {    \
  280.         ERROR((val)->Value);    \
  281.     } else    \
  282.         ERROR(NON_BOOL);
  283.  
  284.  
  285. #define TO_RNG(val) \
  286.     if((val)->type==TYP_RNG) \
  287.         ; \
  288.     else if((val)->type==TYP_ERR) {\
  289.         ERROR((val)->Value); \
  290.     } else \
  291.         ERROR(NON_RANGE);
  292.  
  293. #endif
  294.  
  295. #define TO_ANY(val) \
  296.     if((val)->type==TYP_RNG) \
  297.         ERROR(BAD_INPUT); \
  298.  
  299. #define PUSH_ANY(cp)                \
  300.     if(!cp || !GET_TYP(cp)) {        \
  301.         p->type=0;            \
  302.         p->Int=0;            \
  303.     } else {                \
  304.         p->type=GET_TYP(cp);        \
  305.         p->x=cp->c_z;            \
  306.     }
  307.  
  308. void
  309. init_eval ()
  310. {
  311.   stack = (struct value *) ck_malloc (20 * sizeof (struct value));
  312.   stackmax = 20;
  313.   curstack = 0;
  314.   current_cycle++;
  315. #ifndef __TURBOC__
  316.   (void) signal (SIGFPE, math_sig);
  317. #endif
  318. }
  319.  
  320. /* This huge function takes a byte-compiled expression and executes it. */
  321. struct value *
  322. eval_expression (expr)
  323.      unsigned char *expr;
  324. {
  325.   unsigned char byte;
  326.   unsigned numarg;
  327.   unsigned jumpto;
  328.   struct function *f;
  329.   struct value *p;
  330.   char *strptr;
  331.   int tmp;
  332.  
  333.   CELLREF lrow, hrow, crow;
  334.   CELLREF lcol, hcol, ccol;
  335.  
  336.   struct cell *cell_ptr;
  337.  
  338.   if (!expr)
  339.     return 0;
  340.   jumpto = 0;
  341.   numarg = 0;
  342.   p = 0;
  343.   curstack = 0;
  344.   while ((byte = *expr++) != ENDCOMP)
  345.     {
  346.       if (byte < USR1)
  347.     f = &the_funs[byte];
  348.       else if (byte < SKIP)
  349.     {
  350. #ifdef TEST
  351.       if (byte - USR1 >= n_usr_funs)
  352.         panic ("Only have %d usr-function slots, but found byte for slot %d", n_usr_funs, 1 + byte - USR1);
  353. #endif
  354.       tmp = *expr++;
  355.       f = &usr_funs[byte - USR1][tmp];
  356.     }
  357.       else
  358.     f = &skip_funs[byte - SKIP];
  359.  
  360.       if (f->fn_argn & X_J)
  361.     jumpto = *expr++;
  362.       else if (f->fn_argn & X_JL)
  363.     {
  364.       jumpto = expr[0] + ((unsigned) (expr[1]) << 8);
  365.       expr += 2;
  366.     }
  367.  
  368.       switch (f->fn_argn & X_ARGS)
  369.     {
  370.       /* A0 is special, since it makes the stack grow, while
  371.                all the others make the stack the same size or
  372.                less. . . */
  373.     case X_A0:
  374.       numarg = 0;
  375.       if (curstack == stackmax)
  376.         {
  377.           stackmax *= 2;
  378.           stack = (struct value *) ck_realloc (stack, sizeof (struct value) * stackmax);
  379.         }
  380.       p = &stack[curstack];
  381.       curstack++;
  382.       break;
  383.  
  384.     case X_A1:
  385.       numarg = 1;
  386.       break;
  387.  
  388.     case X_A2:
  389.       numarg = 2;
  390.       break;
  391.     case X_A3:
  392.       numarg = 3;
  393.       break;
  394.     case X_A4:
  395.       numarg = 4;
  396.       break;
  397.     case X_AN:
  398.       numarg = *expr++;
  399.       break;
  400.     default:
  401.       numarg = 0;
  402.       p = 0;
  403. #ifdef TEST
  404.       panic ("Unknown arg_num %d", f->fn_argn);
  405. #endif
  406.     }
  407.       if (numarg > 0)
  408.     {
  409.       int xt;
  410.  
  411. #ifdef TEST
  412.       if (curstack < numarg)
  413.         panic ("Only %u values on stack, not %u", curstack, numarg);
  414. #endif
  415.       p = &stack[curstack - numarg];
  416.       curstack -= (numarg - 1);
  417.       for (xt = 0; xt < numarg; xt++)
  418.         {
  419.           switch (f->fn_argt[xt <= 3 ? xt : 3])
  420.         {
  421.           /* A is for anything */
  422.           /* Any non-range value */
  423.         case 'A':
  424.           TO_ANY (p + xt);
  425.           break;
  426.           /* B is for boolean */
  427.         case 'B':
  428.           TO_BOL (p + xt);
  429.           break;
  430.           /* D is for Don't check */
  431.         case 'D':
  432.           break;
  433.           /* E is for Everything */
  434.         case 'E':
  435.           break;
  436.           /* F is for Float */
  437.         case 'F':
  438.           TO_FLT (p + xt);
  439.           break;
  440.           /* I is for Int */
  441.         case 'I':
  442.           TO_INT (p + xt);
  443.           break;
  444.           /* N is for Number (int or float) */
  445.         case 'N':
  446.           TO_NUM (p + xt);
  447.           break;
  448.           /* R is for Range */
  449.         case 'R':
  450.           TO_RNG (p + xt);
  451.           break;
  452.           /* S is for String */
  453.         case 'S':
  454.           TO_STR (p + xt);
  455.           break;
  456. #ifdef TEST
  457.         default:
  458.           io_error_msg ("YIKE!  Unknown argtype for Fun %u  arg #%u", byte, xt);
  459.           break;
  460. #endif
  461.         }
  462.         }
  463.     }
  464.  
  465.       switch (byte)
  466.     {
  467.     case IF_L:
  468.     case F_IF_L:
  469.     case IF:
  470.     case F_IF:
  471.       if (p->type != TYP_BOL)
  472.         {
  473.           if (p->type != TYP_ERR)
  474.         {
  475.           p->type = TYP_ERR;
  476.           p->Value = NON_BOOL;
  477.         }
  478.           expr += jumpto;
  479.           if (expr[-2] != SKIP)
  480.         jumpto = expr[-1] + (((unsigned) expr[-2]) << 8);
  481.           else
  482.         jumpto = expr[-1];
  483.           expr += jumpto;    /* Skip both branches of the if */
  484.  
  485.         }
  486.       else if (p->Value == 0)
  487.         {
  488.           expr += jumpto;
  489.           --curstack;
  490.         }
  491.       else
  492.         --curstack;
  493.       break;
  494.  
  495.     case SKIP_L:
  496.     case SKIP:
  497.       --curstack;
  498.       expr += jumpto;
  499.       break;
  500.  
  501.     case AND_L:
  502.     case AND:
  503.       if (p->type == TYP_ERR)
  504.         expr += jumpto;
  505.       else if (p->type != TYP_BOL)
  506.         {
  507.           p->type = TYP_ERR;
  508.           p->Value = NON_BOOL;
  509.           expr += jumpto;
  510.         }
  511.       else if (p->Value == 0)
  512.         expr += jumpto;
  513.       else
  514.         --curstack;
  515.       break;
  516.  
  517.     case OR_L:
  518.     case OR:
  519.       if (p->type == TYP_ERR)
  520.         expr += jumpto;
  521.       else if (p->type != TYP_BOL)
  522.         {
  523.           p->type = TYP_ERR;
  524.           p->Value = NON_BOOL;
  525.           expr += jumpto;
  526.         }
  527.       else if (p->Value)
  528.         expr += jumpto;
  529.       else
  530.         --curstack;
  531.       break;
  532.  
  533.     case CONST_FLT:
  534.       p->type = TYP_FLT;
  535.       bcopy ((VOIDSTAR) expr, (VOIDSTAR) (&(p->Float)), sizeof (double));
  536.       expr += sizeof (double);
  537.       break;
  538.  
  539.     case CONST_INT:
  540.       p->type = TYP_INT;
  541.       bcopy ((VOIDSTAR) expr, (VOIDSTAR) (&(p->Int)), sizeof (long));
  542.       expr += sizeof (long);
  543.       break;
  544.  
  545.     case CONST_STR:
  546.     case CONST_STR_L:
  547.       p->type = TYP_STR;
  548.       p->String = (char *) expr + jumpto;
  549.       break;
  550.  
  551.     case CONST_ERR:
  552.       p->type = TYP_ERR;
  553.       p->Value = *expr++;
  554.       /* expr+=sizeof(char *); */
  555.       break;
  556.  
  557.     case CONST_INF:
  558.     case CONST_NINF:
  559.     case CONST_NAN:
  560.       p->type = TYP_FLT;
  561.       p->Float = (byte == CONST_INF) ? __plinf : ((byte == CONST_NINF) ? __neinf : __nan);
  562.       break;
  563.  
  564.     case VAR:
  565.       {
  566.         struct var *varp;
  567.  
  568.         bcopy ((VOIDSTAR) expr, (VOIDSTAR) (&varp), sizeof (struct var *));
  569.         expr += sizeof (struct var *);
  570.         switch (varp->var_flags)
  571.           {
  572.           case VAR_UNDEF:
  573.         p->type = TYP_ERR;
  574.         p->Value = BAD_NAME;
  575.         break;
  576.  
  577.           case VAR_CELL:
  578.         cell_ptr = find_cell (varp->v_rng.lr, varp->v_rng.lc);
  579.         PUSH_ANY (cell_ptr);
  580.         break;
  581.  
  582.           case VAR_RANGE:
  583.         if (varp->v_rng.lr == varp->v_rng.hr && varp->v_rng.lc == varp->v_rng.hc)
  584.           {
  585.             cell_ptr = find_cell (varp->v_rng.lr, varp->v_rng.lc);
  586.             PUSH_ANY (cell_ptr);
  587.           }
  588.         else
  589.           {
  590.             p->type = TYP_RNG;
  591.             p->Rng = varp->v_rng;
  592.           }
  593.         break;
  594. #ifdef TEST
  595.           default:
  596.         panic ("Unknown var type %d", varp->var_flags);
  597. #endif
  598.           }
  599.       }
  600.       break;
  601.  
  602.       /* Cell refs */
  603.     case R_CELL:
  604.     case R_CELL | COLREL:
  605.     case R_CELL | ROWREL:
  606.     case R_CELL | ROWREL | COLREL:
  607.       {
  608.         CELLREF torow, tocol;
  609.  
  610.         torow = GET_ROW (expr);
  611.         tocol = GET_COL (expr);
  612.         expr += EXP_ADD;
  613.         cell_ptr = find_cell ((CELLREF) torow, (CELLREF) tocol);
  614.         PUSH_ANY (cell_ptr);
  615.       }
  616.       break;
  617.  
  618.     case RANGE:
  619.     case RANGE | LRREL:
  620.     case RANGE | LRREL | LCREL:
  621.     case RANGE | LRREL | LCREL | HCREL:
  622.     case RANGE | LRREL | HCREL:
  623.     case RANGE | LRREL | HRREL:
  624.     case RANGE | LRREL | HRREL | LCREL:
  625.     case RANGE | LRREL | HRREL | LCREL | HCREL:
  626.     case RANGE | LRREL | HRREL | HCREL:
  627.     case RANGE | HRREL:
  628.     case RANGE | HRREL | LCREL:
  629.     case RANGE | HRREL | LCREL | HCREL:
  630.     case RANGE | HRREL | HCREL:
  631.     case RANGE | LCREL:
  632.     case RANGE | LCREL | HCREL:
  633.     case RANGE | HCREL:
  634.       p->type = TYP_RNG;
  635.       GET_RNG (expr, &(p->Rng));
  636.       expr += EXP_ADD_RNG;
  637.       break;
  638.  
  639.     case F_TRUE:
  640.     case F_FALSE:
  641.       p->type = TYP_BOL;
  642.       p->Value = (byte == F_TRUE);
  643.       break;
  644.  
  645.     case F_PI:
  646.       p->type = TYP_FLT;
  647.       p->Float = PI;
  648.       break;
  649.  
  650.     case F_ROW:
  651.     case F_COL:
  652.       p->type = TYP_INT;
  653.       p->Int = ((byte == F_ROW) ? cur_row : cur_col);
  654.       break;
  655.  
  656.     case F_NOW:
  657.       p->type = TYP_INT;
  658.       p->Int = time ((VOIDSTAR) 0);
  659.       break;
  660.  
  661.       /* Single operand instrs */
  662.     case F_ABS:
  663.     case F_ACOS:
  664.     case F_ASIN:
  665.     case F_ATAN:
  666.     case F_CEIL:
  667.     case F_COS:
  668.     case F_DTR:
  669.     case F_EXP:
  670.     case F_FLOOR:
  671.     case F_INT:
  672.     case F_LOG:
  673.     case F_LOG10:
  674.     case F_RTD:
  675.     case F_SIN:
  676.     case F_SQRT:
  677.     case F_TAN:
  678.       {
  679. #ifdef __STDC__
  680.         double (*funp1) (double);
  681.         funp1 = (double (*)(double)) (f->fn_fun);
  682. #else
  683.         double (*funp1) ();
  684.         funp1 = (double (*)()) (f->fn_fun);
  685. #endif
  686.  
  687.         p->Float = (*funp1) (p->Float);
  688.         if (p->Float != p->Float)
  689.           ERROR (OUT_OF_RANGE);
  690.       }
  691.       break;
  692.  
  693.     case F_CTIME:
  694.       p->type = TYP_STR;
  695.       strptr = ctime ((time_t*) &p->Int);
  696.       p->String = obstack_alloc (&tmp_mem, 25);
  697.       strncpy (p->String, strptr, 24);
  698.       p->String[24] = '\0';
  699.       break;
  700.  
  701.     case NEGATE:
  702.     case F_NEG:
  703.       if (p->type == TYP_ERR)
  704.         break;
  705.       if (p->type == TYP_INT)
  706.         p->Int = -(p->Int);
  707.       else if (p->type == TYP_FLT)
  708.         p->Float = -(p->Float);
  709.       else
  710.         ERROR (NON_NUMBER);
  711.       break;
  712.  
  713.     case F_RND:
  714.       p->Int = (random () % (p->Int)) + 1;
  715.       break;
  716.  
  717.     case NOT:
  718.     case F_NOT:
  719.       p->Value = !(p->Value);
  720.       break;
  721.  
  722.     case F_ISERR:
  723.       p->Value = (p->type == TYP_ERR);
  724.       p->type = TYP_BOL;
  725.       break;
  726.  
  727.     case F_ISNUM:
  728.       if (p->type == TYP_FLT || p->type == TYP_INT)
  729.         p->Value = 1;
  730.       else if (p->type == TYP_STR)
  731.         {
  732.           strptr = p->String;
  733.           (void) astof (&strptr);
  734.           p->Value = (*strptr == '\0');
  735.         }
  736.       else
  737.         p->Value = 0;
  738.       p->type = TYP_BOL;
  739.       break;
  740.  
  741.     case F_ROWS:
  742.     case F_COLS:
  743.       p->type = TYP_INT;
  744.       p->Int = 1 + (byte == F_ROWS ? (p->Rng.hr - p->Rng.lr) : (p->Rng.hc - p->Rng.lc));
  745.       break;
  746.  
  747.       /* Two operand cmds */
  748.     case F_ATAN2:
  749.     case F_HYPOT:
  750.     case POW:
  751.       {
  752. #ifdef __STDC__
  753.         double (*funp2) (double, double);
  754.         funp2 = (double (*)(double, double)) (f->fn_fun);
  755. #else
  756.         double (*funp2) ();
  757.         funp2 = (double (*)()) (f->fn_fun);
  758. #endif
  759.  
  760.         p->Float = (*funp2) (p->Float, (p + 1)->Float);
  761.         if (p->Float != p->Float)
  762.           ERROR (OUT_OF_RANGE);
  763.       }
  764.       break;
  765.  
  766.     case DIFF:
  767.     case DIV:
  768.     case MOD:
  769.     case PROD:
  770.     case SUM:
  771.  
  772.       if (p->type != (p + 1)->type)
  773.         {
  774.           if (p->type == TYP_INT)
  775.         {
  776.           p->type = TYP_FLT;
  777.           p->Float = (double) p->Int;
  778.         }
  779.           if ((p + 1)->type == TYP_INT)
  780.         {
  781.           (p + 1)->type = TYP_FLT;
  782.           (p + 1)->Float = (double) ((p + 1)->Int);
  783.         }
  784.         }
  785.       if (p->type == TYP_INT)
  786.         {
  787.           switch (byte)
  788.         {
  789.         case DIFF:
  790.           I_SUB (p->Int, (p + 1)->Int);
  791.           break;
  792.         case DIV:
  793.           if ((p + 1)->Int == 0)
  794.             ERROR (DIV_ZERO);
  795.           I_DIV (p->Int, (p + 1)->Int);
  796.           break;
  797.         case MOD:
  798.           if ((p + 1)->Int == 0)
  799.             ERROR (DIV_ZERO);
  800.           I_MOD (p->Int, (p + 1)->Int);
  801.           break;
  802.         case PROD:
  803.           I_MUL (p->Int, (p + 1)->Int);
  804.           break;
  805.         case SUM:
  806.           I_ADD (p->Int, (p + 1)->Int);
  807.           break;
  808. #ifdef TEST
  809.         default:
  810.           panic ("Evaluator confused by byte-value %d", byte);
  811. #endif
  812.         }
  813.         }
  814.       else
  815.         {
  816.           switch (byte)
  817.         {
  818.         case DIFF:
  819.           F_SUB (p->Float, (p + 1)->Float);
  820.           break;
  821.         case DIV:
  822.           if ((p + 1)->Float == 0)
  823.             ERROR (DIV_ZERO);
  824.           F_DIV (p->Float, (p + 1)->Float);
  825.           break;
  826.         case MOD:
  827.           if ((p + 1)->Float == 0)
  828.             ERROR (DIV_ZERO);
  829.           F_MOD (p->Float, (p + 1)->Float);
  830.           break;
  831.         case PROD:
  832.           F_MUL (p->Float, (p + 1)->Float);
  833.           break;
  834.         case SUM:
  835.           F_ADD (p->Float, (p + 1)->Float);
  836.           break;
  837. #ifdef TEST
  838.         default:
  839.           panic ("Unknown operation %d", byte);
  840. #endif
  841.         }
  842.         }
  843.       if (overflow)
  844.         ERROR (OUT_OF_RANGE);
  845.       break;
  846.  
  847.     case EQUAL:
  848.     case NOTEQUAL:
  849.  
  850.     case GREATEQ:
  851.     case GREATER:
  852.     case LESS:
  853.     case LESSEQ:
  854.       if (p->type == TYP_ERR)
  855.         break;
  856.       if ((p + 1)->type == TYP_ERR)
  857.         ERROR ((p + 1)->Value);
  858.  
  859.       if (p->type == TYP_BOL || (p + 1)->type == TYP_BOL)
  860.         {
  861.           if (p->type != (p + 1)->type || (byte != EQUAL && byte != NOTEQUAL))
  862.         ERROR (BAD_INPUT);
  863.           if (byte == EQUAL)
  864.         p->Value = p->Value == (p + 1)->Value;
  865.           else
  866.         p->Value = p->Value != (p + 1)->Value;
  867.           break;
  868.         }
  869.       if (p->type != (p + 1)->type)
  870.         {
  871.           if (p->type == 0)
  872.         {
  873.           if ((p + 1)->type == TYP_STR)
  874.             {
  875.               p->type = TYP_STR;
  876.               p->String = "";
  877.             }
  878.           else if ((p + 1)->type == TYP_INT)
  879.             {
  880.               p->type = TYP_INT;
  881.               p->Int = 0;
  882.             }
  883.           else
  884.             {
  885.               p->type = TYP_FLT;
  886.               p->Float = 0.0;
  887.             }
  888.         }
  889.           else if ((p + 1)->type == 0)
  890.         {
  891.           if (p->type == TYP_STR)
  892.             {
  893.               (p + 1)->type = TYP_STR;
  894.               (p + 1)->String = "";
  895.             }
  896.           else if (p->type == TYP_INT)
  897.             {
  898.               (p + 1)->type = TYP_INT;
  899.               (p + 1)->Int = 0;
  900.             }
  901.           else
  902.             {
  903.               (p + 1)->type = TYP_FLT;
  904.               (p + 1)->Float = 0.0;
  905.             }
  906.         }
  907.           else if (p->type == TYP_STR)
  908.         {
  909.           strptr = p->String;
  910.           if ((p + 1)->type == TYP_INT)
  911.             {
  912.               p->type = TYP_INT;
  913.               p->Int = astol (&strptr);
  914.             }
  915.           else
  916.             {
  917.               p->type = TYP_FLT;
  918.               p->Float = astof (&strptr);
  919.             }
  920.           if (*strptr)
  921.             {
  922.               p->type = TYP_BOL;
  923.               p->Value = (byte == NOTEQUAL);
  924.               break;
  925.             }
  926.         }
  927.           else if ((p + 1)->type == TYP_STR)
  928.         {
  929.           strptr = (p + 1)->String;
  930.           if (p->type == TYP_INT)
  931.             (p + 1)->Int = astol (&strptr);
  932.           else
  933.             (p + 1)->Float = astof (&strptr);
  934.           if (*strptr)
  935.             {
  936.               p->type = TYP_BOL;
  937.               p->Value = (byte == NOTEQUAL);
  938.               break;
  939.             }
  940.  
  941.           /* If we get here, one is INT, and the other
  942.                    is FLT  Make them both FLT */
  943.         }
  944.           else if (p->type == TYP_INT)
  945.         {
  946.           p->type = TYP_FLT;
  947.           p->Float = (double) p->Int;
  948.         }
  949.           else
  950.         (p + 1)->Float = (double) (p + 1)->Int;
  951.         }
  952.       if (p->type == TYP_STR)
  953.         tmp = strcmp (p->String, (p + 1)->String);
  954.       else if (p->type == TYP_FLT)
  955.         tmp = (p->Float < (p + 1)->Float) ? -1 : ((p->Float > (p + 1)->Float) ? 1 : 0);
  956.       else if (p->type == TYP_INT)
  957.         tmp = (p->Int < (p + 1)->Int ? -1 : ((p->Int > (p + 1)->Int) ? 1 : 0));
  958.       else if (p->type == 0)
  959.         tmp = 0;
  960.       else
  961.         {
  962.           tmp = 0;
  963.           panic ("Bad type value %d", p->type);
  964.         }
  965.       p->type = TYP_BOL;
  966.       if (tmp < 0)
  967.         p->Value = (byte == NOTEQUAL || byte == LESS || byte == LESSEQ);
  968.       else if (tmp == 0)
  969.         p->Value = (byte == EQUAL || byte == GREATEQ || byte == LESSEQ);
  970.       else
  971.         p->Value = (byte == NOTEQUAL || byte == GREATER || byte == GREATEQ);
  972.       break;
  973.  
  974.     case F_FIXED:
  975.       tmp = (p + 1)->Int;
  976.       if (tmp < -29 || tmp > 29)
  977.         ERROR (OUT_OF_RANGE);
  978.       if (tmp < 0)
  979.         p->Float = rint ((p->Float) / exp10_arr[-tmp]) * exp10_arr[-tmp];
  980.       else
  981.         p->Float = rint ((p->Float) * exp10_arr[tmp]) / exp10_arr[tmp];
  982.       break;
  983.  
  984.     case F_IFERR:
  985.       if (p->type == TYP_ERR)
  986.         *p = *(p + 1);
  987.       break;
  988.  
  989.     case F_INDEX:
  990.       tmp = (p + 1)->Int - 1;
  991.       if (tmp < 0)
  992.         ERROR (OUT_OF_RANGE);
  993.       lrow = p->Rng.lr;
  994.       lcol = p->Rng.lc;
  995.       hrow = p->Rng.hr;
  996.       hcol = p->Rng.hc;
  997.       if (lrow != hrow && lcol != hcol)
  998.         {
  999.           int dex;
  1000.  
  1001.           dex = 1 + hrow - lrow;
  1002.           if (tmp >= dex * (1 + hcol - lcol))
  1003.         ERROR (OUT_OF_RANGE);
  1004.           crow = tmp % dex;
  1005.           ccol = tmp / dex;
  1006.           lrow += crow;
  1007.           lcol += ccol;
  1008.         }
  1009.       else if (lrow != hrow)
  1010.         {
  1011.           if (tmp > (hrow - lrow))
  1012.         ERROR (OUT_OF_RANGE);
  1013.           lrow += tmp;
  1014.         }
  1015.       else
  1016.         {
  1017.           if (tmp > (hcol - lcol))
  1018.         ERROR (OUT_OF_RANGE);
  1019.           lcol += tmp;
  1020.         }
  1021.       cell_ptr = find_cell (lrow, lcol);
  1022.       PUSH_ANY (cell_ptr);
  1023.       break;
  1024.  
  1025.     case F_INDEX2:
  1026.       crow = (p + 1)->Int - 1;
  1027.       ccol = (p + 2)->Int - 1;
  1028.       lrow = p->Rng.lr;
  1029.       lcol = p->Rng.lc;
  1030.       hrow = p->Rng.hr;
  1031.       hcol = p->Rng.hc;
  1032.       if (crow > (hrow - lrow) || ccol > (hcol - lcol)) 
  1033.         ERROR (OUT_OF_RANGE);
  1034.       cell_ptr = find_cell (lrow + crow, lcol + ccol);
  1035.       PUSH_ANY (cell_ptr);
  1036.       break;
  1037.  
  1038.       /* case F_PRINTF:
  1039.             panic("no printf yet");
  1040.             break; */
  1041.  
  1042.     case CONCAT:
  1043.       strptr = (char *) obstack_alloc (&tmp_mem, strlen (p->String) + strlen ((p + 1)->String) + 1);
  1044.       strcpy (strptr, p->String);
  1045.       strcat (strptr, (p + 1)->String);
  1046.       p->String = strptr;
  1047.       break;
  1048.  
  1049.     case F_ONEOF:
  1050.       if (numarg < 2)
  1051.         ERROR (NO_VALUES);
  1052.       --numarg;
  1053.       tmp = p->Int;
  1054.       if (tmp < 1 || tmp > numarg)
  1055.         ERROR (OUT_OF_RANGE);
  1056.       /* Can never happen? */
  1057.       TO_ANY (p + tmp);
  1058.       p[0] = p[tmp];
  1059.       break;
  1060.  
  1061.     case F_FILE:
  1062.       {
  1063.         FILE *fp;
  1064.         char buf[128];
  1065.         int num;
  1066.  
  1067.         if (numarg < 1)
  1068.           ERROR (NO_VALUES);
  1069.         fp = fopen (p->String, "r");
  1070.         if (!fp)
  1071.           ERROR (BAD_INPUT);
  1072.         switch (numarg)
  1073.           {
  1074.           case 2:
  1075.         fseek (fp, (p + 1)->Int, 0);
  1076.         /* Fallthrough */
  1077.  
  1078.           case 1:
  1079.         while ((num = fread (buf, sizeof (char), sizeof (buf), fp)) > 0)
  1080.             (void) obstack_grow (&tmp_mem, buf, num);
  1081.         break;
  1082.  
  1083.           case 3:
  1084.         fseek (fp, (p + 1)->Int, 0);
  1085.         for (;;)
  1086.           {
  1087.             num = ((p + 2)->Int < sizeof (buf)) ? (p + 2)->Int : sizeof (buf);
  1088.             (p + 2)->Int -= num;
  1089.             num = fread (buf, sizeof (char), num, fp);
  1090.             (void) obstack_grow (&tmp_mem, buf, num);
  1091.             if (num == 0 || (p + 2)->Int == 0)
  1092.               break;
  1093.           }
  1094.         break;
  1095.  
  1096.           default:
  1097.         ERROR (BAD_INPUT);
  1098.           }
  1099.         fclose (fp);
  1100.         (void) obstack_1grow (&tmp_mem, 0);
  1101.         p->String = obstack_finish (&tmp_mem);
  1102.         break;
  1103.       }
  1104.  
  1105.     case AREA_SUM:
  1106.     case AREA_PROD:
  1107.     case AREA_AVG:
  1108.     case AREA_STD:
  1109.     case AREA_MAX:
  1110.     case AREA_MIN:
  1111.     case AREA_CNT:
  1112.     case AREA_VAR:
  1113.       tmp = deal_area (byte, numarg, p);
  1114.       if (tmp)
  1115.         ERROR (tmp);
  1116.       break;
  1117.  
  1118.       /* This is now a fallthrough for all the USRmumble codes */
  1119.     case USR1:
  1120.     default:
  1121.       if ((f->fn_argn & X_ARGS) == X_AN)
  1122.         {
  1123. #ifdef __STDC__
  1124.           void (*funp) (int, struct value *);
  1125.           funp = (void (*)(int, struct value *)) f->fn_fun;
  1126. #else
  1127.           void (*funp) ();
  1128.           funp = (void (*)()) f->fn_fun;
  1129. #endif
  1130.           (*funp) (numarg, p);
  1131.         }
  1132.       else
  1133.         {
  1134. #ifdef __STDC__
  1135.           void (*funp) (struct value *);
  1136.           funp = (void (*)(struct value *)) f->fn_fun;
  1137. #else
  1138.           void (*funp) ();
  1139.           funp = (void (*)()) f->fn_fun;
  1140. #endif
  1141.           (*funp) (p);
  1142.         }
  1143.       break;
  1144.  
  1145.       /* #ifdef TEST
  1146.         default:
  1147.             panic("Unknown byte-value %d",byte);
  1148.             break;
  1149. #endif */
  1150.     }
  1151.       /* Goto next-byte is the equiv of a multi-level break, which
  1152.            C doesn't allow. */
  1153.     next_byte:
  1154.       ;
  1155.     }
  1156. #ifdef TEST
  1157.   if (curstack != 1)
  1158.     io_error_msg ("%d values on stack", curstack);
  1159. #endif
  1160.   return stack;
  1161. }
  1162.  
  1163. /* These helper functions were split out so that eval_expression would compile
  1164.    under Turbo C 2.0 on my PC.
  1165.  */
  1166.  
  1167.  
  1168. static int cnt_flt;
  1169. static int cnt_int;
  1170.  
  1171. static long int_tmp;
  1172. static double flt_tmp;
  1173.  
  1174. static long sqr_int_tmp;    /* for AREA_STD */
  1175. static double sqr_flt_tmp;
  1176.  
  1177. static unsigned char area_cmd;
  1178.  
  1179. static int
  1180. deal_area (cmd, num_args, p)
  1181.      unsigned char cmd;
  1182.      unsigned char num_args;
  1183.      struct value *p;
  1184. {
  1185.   double flt_cnt_flt;
  1186.   CELL *cell_ptr;
  1187.   char *strptr;
  1188.  
  1189.   area_cmd = cmd;
  1190.   cnt_flt = 0;
  1191.   cnt_int = 0;
  1192.   for (; num_args--;)
  1193.     {
  1194.       switch (p[num_args].type)
  1195.     {
  1196.     case TYP_INT:
  1197.       add_int (p[num_args].Int);
  1198.       break;
  1199.  
  1200.     case TYP_FLT:
  1201.       add_flt (p[num_args].Float);
  1202.       break;
  1203.  
  1204.     case TYP_STR:
  1205.       strptr = p[num_args].String;
  1206.       flt_cnt_flt = astof (&strptr);
  1207.       if (*strptr)
  1208.         return NON_NUMBER;
  1209.       add_flt (flt_cnt_flt);
  1210.       break;
  1211.  
  1212.     case TYP_RNG:
  1213.       find_cells_in_range (&(p[num_args].Rng));
  1214.       while (cell_ptr = next_cell_in_range ())
  1215.         {
  1216.           if (GET_TYP (cell_ptr) == TYP_FLT)
  1217.         add_flt (cell_ptr->cell_flt);
  1218.           else if (GET_TYP (cell_ptr) == TYP_INT)
  1219.         add_int (cell_ptr->cell_int);
  1220.           else if (GET_TYP (cell_ptr) == TYP_STR)
  1221.         {
  1222.           strptr = cell_ptr->cell_str;
  1223.           flt_cnt_flt = astof (&strptr);
  1224.           if (!*strptr)
  1225.             add_flt (flt_cnt_flt);
  1226.         }
  1227.         }
  1228.       break;
  1229.  
  1230.     case 0:
  1231.       break;
  1232.  
  1233.     case TYP_ERR:
  1234.       return p[num_args].Value;
  1235.  
  1236.     default:
  1237.       return NON_NUMBER;
  1238.     }
  1239.     }
  1240.   if (!cnt_flt && !cnt_int && area_cmd != AREA_CNT)
  1241.     return NO_VALUES;
  1242.  
  1243.   switch (area_cmd)
  1244.     {
  1245.     case AREA_SUM:
  1246.       if (cnt_flt && cnt_int)
  1247.     {
  1248.       flt_tmp += (double) int_tmp;
  1249.       cnt_int = 0;
  1250.     }
  1251.       break;
  1252.     case AREA_PROD:
  1253.       if (cnt_flt && cnt_int)
  1254.     {
  1255.       flt_tmp *= (double) int_tmp;
  1256.       cnt_int = 0;
  1257.     }
  1258.       break;
  1259.     case AREA_AVG:
  1260.       if (cnt_flt && cnt_int)
  1261.     {
  1262.       flt_tmp += (double) int_tmp;
  1263.       flt_tmp /= (double) ((cnt_flt + cnt_int));
  1264.       cnt_int = 0;
  1265.     }
  1266.       else if (cnt_flt)
  1267.     flt_tmp /= (double) cnt_flt;
  1268.       else
  1269.     {
  1270.       flt_tmp = (double) int_tmp / (double) cnt_int;
  1271.       cnt_int = 0;
  1272.     }
  1273.       break;
  1274.     case AREA_STD:
  1275.       if (cnt_int && cnt_flt)
  1276.     {
  1277.       flt_tmp += (double) int_tmp;
  1278.       sqr_flt_tmp += (double) sqr_int_tmp;
  1279.       cnt_flt += cnt_int;
  1280.       cnt_int = 0;
  1281.     }
  1282.       else if (cnt_int)
  1283.     {
  1284.       flt_tmp = (double) int_tmp;
  1285.       sqr_flt_tmp = (double) sqr_int_tmp;
  1286.       cnt_flt = cnt_int;
  1287.       cnt_int = 0;
  1288.     }
  1289.       flt_cnt_flt = (double) cnt_flt;
  1290.       flt_tmp = sqrt (((flt_cnt_flt * sqr_flt_tmp) -
  1291.                (flt_tmp * flt_tmp)) /
  1292.               (flt_cnt_flt * (flt_cnt_flt - 1)));
  1293.       break;
  1294.     case AREA_VAR:
  1295.       if (cnt_int && cnt_flt)
  1296.     {
  1297.       flt_tmp += (double) int_tmp;
  1298.       sqr_flt_tmp += (double) sqr_int_tmp;
  1299.       cnt_flt += cnt_int;
  1300.       cnt_int = 0;
  1301.     }
  1302.       else if (cnt_int)
  1303.     {
  1304.       flt_tmp = (double) int_tmp;
  1305.       sqr_flt_tmp = (double) sqr_int_tmp;
  1306.       cnt_flt = cnt_int;
  1307.       cnt_int = 0;
  1308.     }
  1309.       flt_cnt_flt = (double) cnt_flt;
  1310.       flt_tmp = ((flt_cnt_flt * sqr_flt_tmp) -
  1311.          (flt_tmp * flt_tmp)) /
  1312.     (flt_cnt_flt * flt_cnt_flt);
  1313.       break;
  1314.  
  1315.     case AREA_MAX:
  1316.       if (cnt_flt && cnt_int && flt_tmp > (double) int_tmp)
  1317.     cnt_int = 0;
  1318.       break;
  1319.  
  1320.     case AREA_MIN:
  1321.       if (cnt_flt && cnt_int && flt_tmp < (double) int_tmp)
  1322.     cnt_int = 0;
  1323.       break;
  1324.  
  1325.     case AREA_CNT:
  1326.       int_tmp = cnt_int + cnt_flt;
  1327.       cnt_int = 1;
  1328.       break;
  1329.  
  1330. #ifdef TEST
  1331.     default:
  1332.       panic ("Unknown AREA command %d", area_cmd);
  1333. #endif
  1334.     }
  1335.   if (cnt_int)
  1336.     {
  1337.       p->type = TYP_INT;
  1338.       p->Int = int_tmp;
  1339.     }
  1340.   else
  1341.     {
  1342.       p->type = TYP_FLT;
  1343.       p->Float = flt_tmp;
  1344.     }
  1345.   return 0;
  1346. }
  1347.  
  1348. static void
  1349. add_flt (value)
  1350.      double value;
  1351. {
  1352.   if (cnt_flt++ == 0)
  1353.     {
  1354.       flt_tmp = value;
  1355.       sqr_flt_tmp = value * value;
  1356.       return;
  1357.     }
  1358.  
  1359.   switch (area_cmd)
  1360.     {
  1361.     case AREA_STD:
  1362.     case AREA_VAR:
  1363.       sqr_flt_tmp += value * value;
  1364.       /* Fall through */
  1365.     case AREA_SUM:
  1366.     case AREA_AVG:
  1367.       flt_tmp += value;
  1368.       return;
  1369.     case AREA_PROD:
  1370.       flt_tmp *= value;
  1371.       return;
  1372.     case AREA_MAX:
  1373.       if (flt_tmp < value)
  1374.     flt_tmp = value;
  1375.       return;
  1376.     case AREA_MIN:
  1377.       if (flt_tmp > value)
  1378.     flt_tmp = value;
  1379.       return;
  1380.     case AREA_CNT:
  1381.       return;
  1382. #ifdef TEST
  1383.     default:
  1384.       panic ("Unknown area command %d in add_flt(%g)", area_cmd, value);
  1385. #endif
  1386.     }
  1387. }
  1388.  
  1389. static void
  1390. add_int (value)
  1391.      long value;
  1392. {
  1393.   if (cnt_int++ == 0)
  1394.     {
  1395.       int_tmp = value;
  1396.       sqr_int_tmp = value * value;
  1397.       return;
  1398.     }
  1399.  
  1400.   switch (area_cmd)
  1401.     {
  1402.     case AREA_STD:
  1403.     case AREA_VAR:
  1404.       sqr_int_tmp += value * value;
  1405.       /* Fall through */
  1406.     case AREA_SUM:
  1407.     case AREA_AVG:
  1408.       int_tmp += value;
  1409.       return;
  1410.     case AREA_PROD:
  1411.       int_tmp *= value;
  1412.       return;
  1413.     case AREA_MAX:
  1414.       if (int_tmp < value)
  1415.     int_tmp = value;
  1416.       return;
  1417.     case AREA_MIN:
  1418.       if (int_tmp > value)
  1419.     int_tmp = value;
  1420.       return;
  1421.     case AREA_CNT:
  1422.       return;
  1423. #ifdef TEST
  1424.     default:
  1425.       panic ("Unknown Area command %d in add_int(%ld)", area_cmd, value);
  1426. #endif
  1427.     }
  1428. }
  1429.  
  1430. #ifdef __STDC__
  1431. double
  1432. dtr (double x)
  1433. #else
  1434. double
  1435. dtr (x)
  1436.      double x;
  1437. #endif
  1438. {
  1439.   return x * (PI / (double) 180.0);
  1440. }
  1441.  
  1442. #ifdef __STDC__
  1443. double
  1444. rtd (double x)
  1445. #else
  1446. double
  1447. rtd (x)
  1448.      double x;
  1449. #endif
  1450. {
  1451.   return x * (180.0 / (double) PI);
  1452. }
  1453.  
  1454. #ifdef __STDC__
  1455. double
  1456. to_int (double x)
  1457. #else
  1458. double
  1459. to_int (x)
  1460.      double x;
  1461. #endif
  1462. {
  1463.   return (x < 0 ? ceil (x) : floor (x));
  1464. }
  1465.  
  1466. /* Various methods of dealing with arithmatic overflow.  They don't work well.
  1467.    Someone should really convince this thing to properly deal with it.
  1468.  */
  1469. #ifdef __TURBOC__
  1470. int
  1471. matherr (exc)
  1472.      struct exception *exc;
  1473. {
  1474.   stack[curstack].type = TYP_ERR;
  1475.   stack[curstack].Value = BAD_INPUT;
  1476.   write (2, "MATHERR\n", 8);
  1477.   return 1;
  1478. }
  1479.  
  1480. #endif
  1481.  
  1482. #ifndef __TURBOC__
  1483. RETSIGTYPE
  1484. math_sig (sig)
  1485.      int sig;
  1486. {
  1487.   stack[curstack].type = TYP_ERR;
  1488.   stack[curstack].Value = BAD_INPUT;
  1489. }
  1490.  
  1491. #endif
  1492.  
  1493. /* Here's the entry point for this module. */
  1494. void
  1495. update_cell (cell)
  1496.      CELL *cell;
  1497. {
  1498.   struct value *new;
  1499.   int new_val;
  1500.  
  1501.   new = eval_expression (cell->cell_formula);
  1502.   if (!new)
  1503.     {
  1504.       push_refs (cell->cell_refs_from);
  1505.       return;
  1506.     }
  1507.   cell->cell_cycle = current_cycle;
  1508.  
  1509.   if (new->type != GET_TYP (cell))
  1510.     {
  1511.       if (GET_TYP (cell) == TYP_STR)
  1512.     free (cell->cell_str);
  1513.       SET_TYP (cell, new->type);
  1514.       new_val = 1;
  1515.       if (new->type == TYP_STR)
  1516.     new->String = strdup (new->String);
  1517.     }
  1518.   else
  1519.     switch (new->type)
  1520.       {
  1521.       case 0:
  1522.     new_val = 0;
  1523.     break;
  1524.       case TYP_FLT:
  1525.     new_val = new->Float != cell->cell_flt;
  1526.     break;
  1527.       case TYP_INT:
  1528.     new_val = new->Int != cell->cell_int;
  1529.     break;
  1530.       case TYP_STR:
  1531.     new_val = strcmp (new->String, cell->cell_str);
  1532.     if (new_val)
  1533.       {
  1534.         free (cell->cell_str);
  1535.         new->String = strdup (new->String);
  1536.       }
  1537.     break;
  1538.       case TYP_BOL:
  1539.     new_val = new->Value != cell->cell_bol;
  1540.     break;
  1541.       case TYP_ERR:
  1542.     new_val = new->Value != cell->cell_err;
  1543.     break;
  1544.       default:
  1545.     new_val = 0;
  1546. #ifdef TEST
  1547.     panic ("Unknown type %d in update_cell", new->type);
  1548. #endif
  1549.       }
  1550.   if (new_val)
  1551.     {
  1552.       cell->c_z = new->x;
  1553.       push_refs (cell->cell_refs_from);
  1554.     }
  1555.   (void) obstack_free (&tmp_mem, tmp_mem_start);
  1556. }
  1557.  
  1558. int
  1559. fls (num)
  1560.      long num;
  1561. {
  1562.   int ret = 1;
  1563.  
  1564.   if (!num)
  1565.     return 0;
  1566.   if (num < 0)
  1567.     num = -num;
  1568.   if (num & 0xffff0000)
  1569.     {
  1570.       ret += 16;
  1571.       num = (num >> 16) & 0xffff;
  1572.     }
  1573.   if (num & 0xff00)
  1574.     {
  1575.       ret += 8;
  1576.       num >>= 8;
  1577.     }
  1578.   if (num & 0xf0)
  1579.     {
  1580.       ret += 4;
  1581.       num >>= 4;
  1582.     }
  1583.   if (num & 0x0c)
  1584.     {
  1585.       ret += 2;
  1586.       num >>= 2;
  1587.     }
  1588.   if (num & 2)
  1589.     ret++;
  1590.   return ret;
  1591. }
  1592.  
  1593. #ifdef SMALLEVAL
  1594. int
  1595. __to_flt (p)
  1596.      struct value *p;
  1597. {
  1598.   char *strptr;
  1599.  
  1600.   switch (p->type)
  1601.     {
  1602.     case 0:
  1603.       p->type = TYP_FLT;
  1604.       p->Float = 0;
  1605.       /* Fallthrough */
  1606.     case TYP_FLT:
  1607.       return 0;
  1608.     case TYP_INT:
  1609.       p->Float = (double) p->Int;
  1610.       p->type = TYP_FLT;
  1611.       return 0;
  1612.     case TYP_STR:
  1613.       p->type = TYP_FLT;
  1614.       strptr = p->String;
  1615.       p->Float = astof (&strptr);
  1616.       if (*strptr)
  1617.     return NON_NUMBER;
  1618.       return 0;
  1619.     case TYP_ERR:
  1620.       return p->Value;
  1621.     default:
  1622.       return NON_NUMBER;
  1623.     }
  1624. }
  1625.  
  1626. int
  1627. __to_int (p)
  1628.      struct value *p;
  1629. {
  1630.   char *strptr;
  1631.  
  1632.   switch (p->type)
  1633.     {
  1634.     case 0:
  1635.       p->type = TYP_INT;
  1636.       p->Int = 0;
  1637.     case TYP_INT:
  1638.       return 0;
  1639.     case TYP_FLT:
  1640.       p->type = TYP_INT;
  1641.       p->Int = (long) p->Float;
  1642.       return 0;
  1643.     case TYP_STR:
  1644.       p->type = TYP_INT;
  1645.       strptr = p->String;
  1646.       p->Int = astol (&strptr);
  1647.       if (*strptr)
  1648.     return NON_NUMBER;
  1649.       return 0;
  1650.     case TYP_ERR:
  1651.       return p->Value;
  1652.     default:
  1653.       return NON_NUMBER;
  1654.     }
  1655. }
  1656.  
  1657. int
  1658. __to_num (p)
  1659.      struct value *p;
  1660. {
  1661.   char *strptr;
  1662.  
  1663.   switch (p->type)
  1664.     {
  1665.     case 0:
  1666.       p->type = TYP_INT;
  1667.       p->Int = 0;
  1668.       return 0;
  1669.     case TYP_FLT:
  1670.     case TYP_INT:
  1671.       return 0;
  1672.     case TYP_STR:
  1673.       p->type = TYP_FLT;
  1674.       strptr = p->String;
  1675.       p->Float = astof (&strptr);
  1676.       if (*strptr)
  1677.     return NON_NUMBER;
  1678.       return 0;
  1679.     case TYP_ERR:
  1680.       return p->Value;
  1681.     default:
  1682.       return NON_NUMBER;
  1683.     }
  1684. }
  1685.  
  1686. int
  1687. __to_str (p)
  1688.      struct value *p;
  1689. {
  1690.   char *strptr;
  1691.  
  1692.   switch (p->type)
  1693.     {
  1694.     case 0:
  1695.       p->type = TYP_STR;
  1696.       p->String = obstack_alloc (&tmp_mem, 1);
  1697.       p->String[0] = '\0';
  1698.       return 0;
  1699.  
  1700.     case TYP_STR:
  1701.       return 0;
  1702.  
  1703.     case TYP_INT:
  1704.       p->type = TYP_STR;
  1705.       strptr = obstack_alloc (&tmp_mem, 30);
  1706.       sprintf (strptr, "%ld", p->Int);
  1707.       p->String = strptr;
  1708.       return 0;
  1709.  
  1710.     case TYP_FLT:
  1711.       p->type = TYP_STR;
  1712.       strptr = flt_to_str (p->Float);
  1713.       (void) obstack_grow (&tmp_mem, strptr, strlen (strptr) + 1);
  1714.       p->String = obstack_finish (&tmp_mem);
  1715.       return 0;
  1716.  
  1717.     case TYP_ERR:
  1718.       return p->Value;
  1719.  
  1720.     default:
  1721.       return NON_STRING;
  1722.     }
  1723. }
  1724.  
  1725. int
  1726. __to_bol (p)
  1727.      struct value *p;
  1728. {
  1729.   switch (p->type)
  1730.     {
  1731.     case TYP_BOL:
  1732.       return 0;
  1733.     case TYP_ERR:
  1734.       return p->Value;
  1735.     default:
  1736.       return NON_BOOL;
  1737.     }
  1738. }
  1739.  
  1740. int
  1741. __to_rng (p)
  1742.      struct value *p;
  1743. {
  1744.   switch (p->type)
  1745.     {
  1746.     case TYP_RNG:
  1747.       return 0;
  1748.     case TYP_ERR:
  1749.       return p->Value;
  1750.     default:
  1751.       return NON_BOOL;
  1752.     }
  1753. }
  1754.  
  1755. #endif
  1756.